{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Learning Tree Structure from Data using the Chow-Liu Algorithm "
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "In this notebook, we show an example for learning the structure of a Bayesian Network using the Chow-Liu algorithm.  We will first build a model to generate some data and then attempt to learn the model's graph structure back from the generated data."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## First, create a tree graph"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "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",
      "text/plain": [
       "<Figure size 432x288 with 1 Axes>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "import networkx as nx\n",
    "import matplotlib.pyplot as plt\n",
    "\n",
    "from pgmpy.models import DiscreteBayesianNetwork\n",
    "\n",
    "# construct the tree graph structure\n",
    "model = DiscreteBayesianNetwork([(\"A\", \"B\"), (\"A\", \"C\"), (\"B\", \"D\"), (\"B\", \"E\"), (\"C\", \"F\")])\n",
    "nx.draw_circular(\n",
    "    model, with_labels=True, arrowsize=30, node_size=800, alpha=0.3, font_weight=\"bold\"\n",
    ")\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Then, add CPDs to our tree to create a Bayesian network"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {},
   "outputs": [],
   "source": [
    "from pgmpy.factors.discrete import TabularCPD\n",
    "\n",
    "# add CPD to each edge\n",
    "cpd_a = TabularCPD(\"A\", 2, [[0.4], [0.6]])\n",
    "cpd_b = TabularCPD(\n",
    "    \"B\", 3, [[0.6, 0.2], [0.3, 0.5], [0.1, 0.3]], evidence=[\"A\"], evidence_card=[2]\n",
    ")\n",
    "cpd_c = TabularCPD(\"C\", 2, [[0.3, 0.4], [0.7, 0.6]], evidence=[\"A\"], evidence_card=[2])\n",
    "cpd_d = TabularCPD(\n",
    "    \"D\",\n",
    "    3,\n",
    "    [[0.5, 0.3, 0.1], [0.4, 0.4, 0.8], [0.1, 0.3, 0.1]],\n",
    "    evidence=[\"B\"],\n",
    "    evidence_card=[3],\n",
    ")\n",
    "cpd_e = TabularCPD(\n",
    "    \"E\", 2, [[0.3, 0.5, 0.2], [0.7, 0.5, 0.8]], evidence=[\"B\"], evidence_card=[3]\n",
    ")\n",
    "cpd_f = TabularCPD(\n",
    "    \"F\", 3, [[0.3, 0.6], [0.5, 0.2], [0.2, 0.2]], evidence=[\"C\"], evidence_card=[2]\n",
    ")\n",
    "model.add_cpds(cpd_a, cpd_b, cpd_c, cpd_d, cpd_e, cpd_f)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Next, generate sample data from our tree Bayesian network"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {},
   "outputs": [
    {
     "name": "stderr",
     "output_type": "stream",
     "text": [
      "Generating for node: D: 100%|██████████| 6/6 [00:00<00:00, 275.41it/s]"
     ]
    },
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "      A  B  C  D  E  F\n",
      "0     0  1  0  2  0  1\n",
      "1     0  0  0  1  1  1\n",
      "2     1  1  0  1  0  1\n",
      "3     1  2  1  1  1  0\n",
      "4     0  0  1  1  0  0\n",
      "...  .. .. .. .. .. ..\n",
      "9995  0  1  1  0  1  0\n",
      "9996  0  0  1  1  1  0\n",
      "9997  1  1  0  2  1  2\n",
      "9998  1  0  0  0  1  0\n",
      "9999  1  1  1  0  1  0\n",
      "\n",
      "[10000 rows x 6 columns]\n"
     ]
    },
    {
     "name": "stderr",
     "output_type": "stream",
     "text": [
      "\n"
     ]
    }
   ],
   "source": [
    "from pgmpy.sampling import BayesianModelSampling\n",
    "\n",
    "# sample data from BN\n",
    "inference = BayesianModelSampling(model)\n",
    "df_data = inference.forward_sample(size=10000)\n",
    "print(df_data)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Finally, apply the Chow-Liu algorithm to learn the tree graph from sample data"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {},
   "outputs": [
    {
     "name": "stderr",
     "output_type": "stream",
     "text": [
      "Building tree: 100%|██████████| 15/15.0 [00:00<00:00, 4518.10it/s]\n"
     ]
    },
    {
     "data": {
      "image/png": "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",
      "text/plain": [
       "<Figure size 432x288 with 1 Axes>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "from pgmpy.estimators import TreeSearch\n",
    "\n",
    "# learn graph structure\n",
    "est = TreeSearch(df_data, root_node=\"A\")\n",
    "dag = est.estimate(estimator_type=\"chow-liu\")\n",
    "nx.draw_circular(\n",
    "    dag, with_labels=True, arrowsize=30, node_size=800, alpha=0.3, font_weight=\"bold\"\n",
    ")\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## To parameterize the learned graph from data, check out the other tutorials for more info"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "[<TabularCPD representing P(A:2) at 0x7f24dd4dbdf0>,\n",
       " <TabularCPD representing P(B:3 | A:2) at 0x7f24dd4d4ee0>,\n",
       " <TabularCPD representing P(C:2 | A:2) at 0x7f24dd4d7790>,\n",
       " <TabularCPD representing P(D:3 | B:3) at 0x7f24dd4d7ee0>,\n",
       " <TabularCPD representing P(E:2 | B:3) at 0x7f24dd4c7cd0>,\n",
       " <TabularCPD representing P(F:3 | C:2) at 0x7f24dd4d7c10>]"
      ]
     },
     "execution_count": 5,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "from pgmpy.estimators import BayesianEstimator\n",
    "\n",
    "# there are many choices of parametrization, here is one example\n",
    "model = DiscreteBayesianNetwork(dag.edges())\n",
    "model.fit(\n",
    "    df_data, estimator=BayesianEstimator, prior_type=\"dirichlet\", pseudo_counts=0.1\n",
    ")\n",
    "model.get_cpds()"
   ]
  }
 ],
 "metadata": {
  "anaconda-cloud": {},
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.8.8"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 1
}
